
#define FDB_LINUX 1 // 区分FDB和Pro环境的，和Win,Linux系统环境无关

#include <node.h>
#include "v8.h"
#include "uv.h"

#undef WINAPI_FAMILY

#include "kernel/dir.h"
#include "kernel/file.h"
#include "kernel/OgreStringVector.h"
#include "udataset/mdb/ModelDB.h"
#include "udataset/mdb/PModelXmlImportor.h"

//#undef String

#include "xmlimportorlistener.h"
#include "connectionoptions.h"
#include "options.h"
#include "taskoptions.h"
#include "wrap.h"

using namespace std;
using namespace v8;
using namespace FD::Utility::Dataset;
using namespace FD::Utility::DB;
using namespace FD::Kernel;

namespace freedatabase
{

using v8::FunctionCallbackInfo;
using v8::Isolate;
using v8::Local;
using v8::Object;
using v8::String;
using v8::Value;

PModelXmlImportor *dbimp = NULL;
ModelDataSource *pSource = NULL;

/**
			 * 解析参数
			 * */
char *LocalObject2char(Local<String> arg)
{
	int len = arg->Utf8Length();
	char *charparam = new char[len + 1];
	arg->WriteUtf8(charparam, len + 1);
	return charparam;
}

/**
				 * XML导入回调
				* */
void import_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	ImportorOptions *opts = (ImportorOptions *)handle->data;
	Local<Value> argv[1];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : v8::Boolean::New(isolate, true);
	// 执行回调函数
	HandleScope scope(isolate);
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 1, argv);
	}
	// 关闭数据库
	if (dbimp != NULL)
	{
		dbimp->closeSourceDB();
		delete dbimp;
	}
	delete opts;
}
/**
				 * XML导入工作线程
				 * **/
void import_async_thread_work(uv_work_t *args)
{
	ImportorOptions *opts = (ImportorOptions *)args->data;
	ConnectionOptions *connOpts = opts->connopts;
	dbimp = new PModelXmlImportor;
	dbimp->openSourceDB(MDBT_MYSQL, connOpts->GetHost().c_str(), connOpts->GetPort(), connOpts->GetDbName().c_str(), connOpts->GetUsername().c_str(), connOpts->GetPassword().c_str());

	//PModel的名称modelName不能重，否则会失败
	//如果存在，则删掉
	dbimp->removePModel(opts->modelname.c_str());

	FD::Kernel::FdStringArray subDir, files;
	Directory::getDirectories(opts->pmodelfolder.c_str(), subDir);

	//遍历目录，假设了目录结构
	StringVector treeXmls, attrXmls;

	for (int i = 0; i < subDir.size(); i++)
	{
		files.removeAll();
		Directory::getFiles(subDir.at(i), files, false, "*.xml");
		if (files.size() != 2)
			continue;

		for (int j = 0; j < files.size(); j++)
		{
			FD::Kernel::FdMultiByteString file = files.at(j);
			if (file.toLower().isTailString("ifc.xml"))
			{
				attrXmls.push_back(file);
			}
			else
			{
				treeXmls.push_back(file);
			}
		}
	}

	//添加 导入的人，模型的名称， 要导入的结构xml和属性xml。默认会给导入人导入模型的权限
	dbimp->setImportPModelXmlFile(opts->author.c_str(), opts->modelname.c_str(), treeXmls, attrXmls);
	dbimp->addListener(new XmlImportorListener());

	//同步工作
	dbimp->executeImport(true);
	opts->ok = true; // 导入成功
}
/**
	 * 导入pModel属性文件
	 * */
void ImportPModelXmlFile(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 5)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[4]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg4 wrong argument type")));
		return;
	}
	// 解析参数
	ConnectionOptions *connOpts = ObjectWrap::Unwrap<ConnectionOptions>(args[3]->ToObject());

	ImportorOptions *opts = new ImportorOptions();
	opts->author = utf82gbk(LocalObject2char(args[0]->ToString()));
	;
	opts->modelname = utf82gbk(LocalObject2char(args[1]->ToString()));
	;
	opts->connopts = connOpts;
	opts->pmodelfolder = utf82gbk(LocalObject2char(args[2]->ToString()));
	;
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[4])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, import_async_thread_work, import_async_thread_callback);
}

/**
	 *
	* */
void database_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	DatabaseOptions *opts = (DatabaseOptions *)handle->data;
	Local<Value> argv[1];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : v8::Boolean::New(isolate, true);
	// 执行回调函数
	HandleScope scope(isolate);
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 1, argv);
	}

	delete opts;
}
/**
	 *
	 * **/
void opendatabase_async_thread_work(uv_work_t *args)
{
	DatabaseOptions *opts = (DatabaseOptions *)args->data;
	ConnectionOptions *connOpts = opts->connopts;
	pSource = ModelDataSourceManager::getSingletonPtr()->openDataSource(MDBT_MYSQL, connOpts->GetHost().c_str(), connOpts->GetPort(), connOpts->GetDbName().c_str(), connOpts->GetUsername().c_str(), connOpts->GetPassword().c_str());
	opts->ok = true;
}
/**
	 * 打开数据库
	 * **/
void OpenDataSource(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 2)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsObject())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	// 解析参数

	ConnectionOptions *connOpts = ObjectWrap::Unwrap<ConnectionOptions>(args[0]->ToObject());

	DatabaseOptions *opts = new DatabaseOptions();
	opts->connopts = connOpts;
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[1])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, opendatabase_async_thread_work, database_async_thread_callback);
}

/**
	 * 关闭数据库
	* **/
void closedatabase_async_thread_work(uv_work_t *args)
{
	DatabaseOptions *opts = (DatabaseOptions *)args->data;
	ModelDataSourceManager::getSingletonPtr()->closeDataSource(pSource);
	opts->ok = true;
}
/**
				 * 关闭数据库
				* **/
void CloseDataSource(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 1)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	// 解析参数
	DatabaseOptions *opts = new DatabaseOptions();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[0])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, closedatabase_async_thread_work, database_async_thread_callback);
}

/**
				 * 查询模型信息回调方法
				 * 异步
				* */
void pmodelinfo_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	PModelInfoOptions *opts = (PModelInfoOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : v8::Boolean::New(isolate, true);
	argv[1] = opts->ok ? PModelInfoVec2Array(isolate, &(opts->infovec)) : v8::Array::New(isolate, 0);
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/**
				* 查询模型信息
				* 异步
				* **/
void pmodelinfo_async_thread_work(uv_work_t *args)
{
	PModelInfoOptions *opts = (PModelInfoOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		opts->ok = modelDB->queryPModelInfo(opts->infovec);
	}
}
/**
				* 获取所有导入的PModel列表
				* */
void QueryPModelInfo(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 1)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	// 解析参数
	PModelInfoOptions *opts = new PModelInfoOptions();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[0])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, pmodelinfo_async_thread_work, pmodelinfo_async_thread_callback);
}

/**
	* 按页查询模型信息
	* 执行
	* **/
void pmodelinfopage_async_thread_work(uv_work_t *args)
{
	PModelInfoOptions *opts = (PModelInfoOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		PModelInfoPage page;
		opts->ok = modelDB->queryPModelInfo_Page(opts->pagecount, page);
		if (opts->pagenumber == 0)
		{
			opts->infovec = page.result;
			opts->totalnumber = page.getTotalNum();
			return;
		}
		//支持直接跳转到某页，没有则返回false
		//默认是pageNo=0， 代表一直往下翻，非0代表直接跳到pageNo页，非法页返回false
		bool bQueryPModelInfo = page.nextPage(opts->pagenumber);
		opts->ok = bQueryPModelInfo;
		if (bQueryPModelInfo)
		{
			opts->infovec = page.result;
			opts->totalnumber = page.getTotalNum();
		}
	}
}
/**
	* 按页查询模型信息回调方法
	* 回调
	* */
void pmodelinfopage_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	PModelInfoOptions *opts = (PModelInfoOptions *)handle->data;
	Local<Value> argv[3];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? Number::New(isolate, opts->totalnumber) : Number::New(isolate, 0);
	argv[2] = opts->ok ? PModelInfoVec2Array(isolate, &(opts->infovec)) : v8::Array::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 3, argv);
	}

	delete opts;
}

/**
	* 分页查询模型信息
	* */
void QueryPModelInfoPage(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	PModelInfoOptions *opts = new PModelInfoOptions();
	opts->pagenumber = Local<Number>::Cast(args[0])->NumberValue();
	opts->pagecount = Local<Number>::Cast(args[1])->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, pmodelinfopage_async_thread_work, pmodelinfopage_async_thread_callback);
}

/**
				* 根据Pmodel名称获取对应的ID
				* 执行
				* **/
void existpmodel_async_thread_work(uv_work_t *args)
{
	PModelOptions *opts = (PModelOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		opts->modelID = modelDB->existsPModel(opts->modelName.c_str());
		opts->ok = true;
	}
}
/**
	* 根据pmodel名称获取对应的ID
	* 回调
	* */
void existpmodel_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	PModelOptions *opts = (PModelOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? Number::New(isolate, opts->modelID) : Number::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/**
				* 根据pmodel名称获取对应的ID
				* */
void ExistsPModel(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 2)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	// 解析参数
	PModelOptions *opts = new PModelOptions();

	opts->modelName = utf82gbk(LocalObject2char(args[0]->ToString()));
	;
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[1])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, existpmodel_async_thread_work, existpmodel_async_thread_callback);
}

/**
	* 验证用户是否有访问模型的权限
	* 执行
	* **/
void auth_async_thread_work(uv_work_t *args)
{
	AuthOptions *opts = (AuthOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		opts->accessed = modelDB->hasPModelPermission(opts->author.c_str(), opts->modelID);
		opts->ok = true;
	}
}
/**
	* 根据pmodel名称获取对应的ID
	* 回调
	* */
void auth_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	AuthOptions *opts = (AuthOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = Boolean::New(isolate, opts->accessed);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/*
				* 验证用户是否有权限访问某数据
				*/
void HasPModelPermission(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	AuthOptions *opts = new AuthOptions();

	opts->author = utf82gbk(LocalObject2char(args[0]->ToString()));
	;
	opts->modelID = args[1]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, auth_async_thread_work, auth_async_thread_callback);
}

/**
 * 查询根节点信息
 * 执行
* **/
void rootnode_async_thread_work(uv_work_t *args)
{
	TreeNodeOptions *opts = (TreeNodeOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		ModelTree *rootTree = NULL;
		bool bQueryRootTree = modelDB->queryPModelRootTree(opts->modelID, rootTree);
		opts->ok = bQueryRootTree;
		if (bQueryRootTree)
		{
			opts->treeNode = rootTree;
		}
	}
}
/**
 * 查询根节点信息
 * 回调
* */
void rootnode_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	TreeNodeOptions *opts = (TreeNodeOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? ModelTree2Object(isolate, opts->treeNode) : v8::Object::New(isolate);
	if (opts->ok)
	{
		ModelDB::releaseModelTree(opts->treeNode);
	}
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}
	delete opts;
}
/**
	 * 查询根节点信息
	* */
void QueryPModelRootTree(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 2)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	// 解析参数
	TreeNodeOptions *opts = new TreeNodeOptions();

	opts->modelID = args[0]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[1])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, rootnode_async_thread_work, rootnode_async_thread_callback);
}

/**
 * 通过GUID查询树节点信息
 * 执行
* **/
void treenode_guid_async_thread_work(uv_work_t *args)
{
	TreeNodeOptions *opts = (TreeNodeOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		ModelTree *rootTree = NULL;
		bool bQueryTreeNode = modelDB->queryPModelTreeByGuid(opts->modelID, opts->guid.c_str(), rootTree);
		opts->ok = bQueryTreeNode;
		if (bQueryTreeNode)
		{
			opts->treeNode = rootTree;
		}
	}
}
/**
 * 通过GUID查询树节点信息
 * 回调
* */
void treenode_guid_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	TreeNodeOptions *opts = (TreeNodeOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	argv[1] = opts->ok ? ModelTree2Object(isolate, opts->treeNode) : v8::Object::New(isolate);
	if (opts->ok)
	{
		ModelDB::releaseModelTree(opts->treeNode);
	}
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}
	delete opts;
}
/**
 * 通过GUID查询树节点信息
* */
void QueryPModelTreeByGuid(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	TreeNodeOptions *opts = new TreeNodeOptions();
	opts->modelID = args[0]->NumberValue();
	opts->guid = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, treenode_guid_async_thread_work, treenode_guid_async_thread_callback);
}

/**
 * 直接根据Guid查询某父节点
 * 执行
* **/
void treenode_guid_parent_async_thread_work(uv_work_t *args)
{
	TreeNodeOptions *opts = (TreeNodeOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		ModelTree *rootTree = NULL;
		bool bQueryTreeNode = modelDB->queryPModelParentTreeByGuid(opts->modelID, opts->guid.c_str(), rootTree);
		opts->ok = bQueryTreeNode;
		if (bQueryTreeNode)
		{
			opts->treeNode = rootTree;
		}
	}
}
/**
 * 直接根据Guid查询某父节点
 * 回调
* */
void treenode_guid_parent_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	TreeNodeOptions *opts = (TreeNodeOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	argv[1] = opts->ok ? ModelTree2Object(isolate, opts->treeNode) : v8::Object::New(isolate);
	if (opts->ok)
	{
		ModelDB::releaseModelTree(opts->treeNode);
	}
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}
	delete opts;
}
/**
 * 直接根据Guid查询某父节点
* */
void QueryPModelParentTreeByGuid(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	TreeNodeOptions *opts = new TreeNodeOptions();
	opts->modelID = args[0]->NumberValue();
	opts->guid = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, treenode_guid_parent_async_thread_work, treenode_guid_parent_async_thread_callback);
}

/**
 * 查询子节点
 * 执行
* **/
void childnode_async_thread_work(uv_work_t *args)
{
	TreeNodeOptions *opts = (TreeNodeOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		ModelTreeVec childTreeVec;
		bool bQueryChildTree = modelDB->queryPModelChildTree(opts->modelID, opts->parentGuid.c_str(), childTreeVec);
		opts->ok = bQueryChildTree;
		if (bQueryChildTree)
		{
			opts->treeNodeVec = childTreeVec;
		}
	}
}
/**
 * 查询子树
 * 回调
* */
void childnode_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	TreeNodeOptions *opts = (TreeNodeOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? ModelTreeVec2Array(isolate, opts->treeNodeVec) : v8::Array::New(isolate, 0);
	if (opts->ok)
	{
		ModelDB::releaseModelTreeVec(opts->treeNodeVec);
	}
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/**
 * 查询子树
 * */
void QueryPModelChildTree(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 4)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	// 解析参数
	TreeNodeOptions *opts = new TreeNodeOptions();

	opts->modelID = args[0]->NumberValue();
	opts->parentGuid = utf82gbk(LocalObject2char(args[1]->ToString()));
	//opts->tileNo = args[2]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[3])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, childnode_async_thread_work, childnode_async_thread_callback);
}

/**
 * 查询子节点--分页
 * 执行
* **/
void childnode_page_async_thread_work(uv_work_t *args)
{
	TreeNodeOptions *opts = (TreeNodeOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		ModelTreePage treePage;
		bool bQueryChildTree = modelDB->queryPModelChildTree_Page(opts->modelID, opts->parentGuid.c_str(), opts->pagecount, treePage);
		if (opts->pagenumber == 0)
		{
			opts->treeNodeVec = treePage.result;
			opts->totalnumber = treePage.getTotalNum();
			return;
		}
		//支持直接跳转到某页，没有则返回false
		//默认是pageNo=0， 代表一直往下翻，非0代表直接跳到pageNo页，非法页返回false
		bQueryChildTree = treePage.nextPage(opts->pagenumber);
		opts->ok = bQueryChildTree;
		if (bQueryChildTree)
		{
			opts->treeNodeVec = treePage.result;
			opts->totalnumber = treePage.getTotalNum();
		}
	}
}
/**
 * 查询子树--分页
 * 回调
* */
void childnode_page_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	TreeNodeOptions *opts = (TreeNodeOptions *)handle->data;
	Local<Value> argv[3];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	argv[1] = opts->ok ? Number::New(isolate, opts->totalnumber) : Number::New(isolate, 0);
	argv[2] = opts->ok ? ModelTreeVec2Array(isolate, opts->treeNodeVec) : v8::Array::New(isolate, 0);
	if (opts->ok)
	{
		ModelDB::releaseModelTreeVec(opts->treeNodeVec);
	}
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 3, argv);
	}
	delete opts;
}
/**
 * 查询子树--分页
 * */
void QueryPModelChildTreePage(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 5)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	if (!args[4]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg4 wrong argument type")));
		return;
	}
	// 解析参数
	TreeNodeOptions *opts = new TreeNodeOptions();

	opts->modelID = args[0]->NumberValue();
	opts->parentGuid = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->pagenumber = args[2]->NumberValue();
	opts->pagecount = args[3]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[4])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, childnode_page_async_thread_work, childnode_page_async_thread_callback);
}

/**
 * 根据构件ID查询构件属性
 * 执行
* **/
void compattr_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompAttr attr;
		bool bQueryCompAttr = modelDB->queryPModelCompAttr(opts->modelID, opts->guid.c_str(), attr);
		opts->ok = bQueryCompAttr;
		if (bQueryCompAttr)
		{
			opts->attr = attr;
		}
	}
}
/**
 * 根据构件ID查询构件属性
 * 回调
* */
void compattr_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? CompAttr2Object(isolate, &(opts->attr)) : v8::Object::New(isolate);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/**
* guid查询属性
* 根据构件ID查询构件属性
* */
void QueryPModelCompAttr(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->guid = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, compattr_async_thread_work, compattr_async_thread_callback);
}

/**
	* 条件查询属性
	* 执行
	* **/
void compbyprop_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompInfoVec infoVec;
		bool bQueryCompByProperty = modelDB->queryPModelCompByProperty(opts->modelID, opts->propKey.c_str(), opts->propVal.c_str(), infoVec);
		opts->ok = bQueryCompByProperty;
		if (bQueryCompByProperty)
		{
			opts->infoVec = infoVec;
		}
	}
}
/**
			* 条件查询属性
			* 回调
			* */
void compbyprop_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? CompInfoVec2Array(isolate, &(opts->infoVec)) : v8::Array::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/**
	* 条件查询属性
	* */
void QueryPModelCompByProperty(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 4)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->propKey = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->propVal = utf82gbk(LocalObject2char(args[2]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[3])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, compbyprop_async_thread_work, compbyprop_async_thread_callback);
}

/**
 * 分页查询属性
 * 执行
* **/
void compbyproppage_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompInfoPage page;
		opts->ok = modelDB->queryPModelCompByProperty_Page(opts->modelID, opts->propKey.c_str(), opts->propVal.c_str(), opts->pagecount, page);
		if (opts->pagenumber == 0)
		{
			opts->infoVec = page.result;
			opts->totalnumber = page.getTotalNum();
			return;
		}
		//支持直接跳转到某页，没有则返回false
		//默认是pageNo=0， 代表一直往下翻，非0代表直接跳到pageNo页，非法页返回false
		bool bQueryPModelInfo = page.nextPage(opts->pagenumber);
		opts->ok = bQueryPModelInfo;
		if (bQueryPModelInfo)
		{
			opts->infoVec = page.result;
			opts->totalnumber = page.getTotalNum();
		}
	}
}
/**
			* 分页查询属性
			* 回调
			* */
void compbyproppage_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[3];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? Number::New(isolate, opts->totalnumber) : Number::New(isolate, 0);
	argv[2] = opts->ok ? CompInfoVec2Array(isolate, &(opts->infoVec)) : v8::Array::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 3, argv);
	}

	delete opts;
}
/**
 * 分页查询属性
* */
void QueryPModelCompByPropertyPage(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 6)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[3]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[4]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[5]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();
	opts->modelID = args[0]->NumberValue();
	opts->propKey = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->propVal = utf82gbk(LocalObject2char(args[2]->ToString()));
	opts->pagenumber = Local<Number>::Cast(args[3])->NumberValue();
	opts->pagecount = Local<Number>::Cast(args[4])->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[5])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, compbyproppage_async_thread_work, compbyproppage_async_thread_callback);
}

/**
			* 查询所有构件类别
			* 执行
			* **/
void comptype_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompTypeVec typeVec;
		bool bQueryCompType = modelDB->queryPModelCompType(opts->modelID, typeVec);
		opts->ok = bQueryCompType;
		if (bQueryCompType)
		{
			opts->typeVec = typeVec;
		}
	}
}
/**
			* 查询所有构件类别
			* 回调
			* */
void comptype_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? CompTypeVec2Array(isolate, &(opts->typeVec)) : v8::Array::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/**
			* 查询所有构件类别
			* */
void QueryPModelCompType(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 2)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[1])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, comptype_async_thread_work, comptype_async_thread_callback);
}

/**
			* 根据构件类别获取构件guid
			* 执行
			* **/
void compbytype_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompInfoVec compInfoVec;
		bool bQueryCompByType = modelDB->queryPModelCompByType(opts->modelID, opts->compTypeId, compInfoVec);
		opts->ok = bQueryCompByType;
		if (bQueryCompByType)
		{
			opts->infoVec = compInfoVec;
		}
	}
}
/**
			* 根据构件类别获取构件guid
			* 回调
			* */
void compbytype_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? CompInfoVec2Array(isolate, &(opts->infoVec)) : v8::Array::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}
/**
			/**
			* 根据构件类别获取构件guid
			* */
void QueryPModelCompByType(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->compTypeId = args[1]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, compbytype_async_thread_work, compbytype_async_thread_callback);
}

/**
			* 根据构件类别获取构件guid---分页
			* 执行
			* **/
void compbytypepage_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompInfoPage page;
		opts->ok = modelDB->queryPModelCompByType_Page(opts->modelID, opts->compTypeId, opts->pagecount, page);
		if (opts->pagenumber == 0)
		{
			opts->infoVec = page.result;
			opts->totalnumber = page.getTotalNum();
			return;
		}
		//支持直接跳转到某页，没有则返回false
		//默认是pageNo=0， 代表一直往下翻，非0代表直接跳到pageNo页，非法页返回false
		bool bQueryPModelInfo = page.nextPage(opts->pagenumber);
		opts->ok = bQueryPModelInfo;
		if (bQueryPModelInfo)
		{
			opts->infoVec = page.result;
			opts->totalnumber = page.getTotalNum();
		}
	}
}
/**
			* 根据构件类别获取构件guid---分页
			* 回调
			* */
void compbytypepage_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? Number::New(isolate, opts->totalnumber) : v8::Number::New(isolate, 0);
	argv[2] = opts->ok ? CompInfoVec2Array(isolate, &(opts->infoVec)) : v8::Array::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 3, argv);
	}

	delete opts;
}
/**
			* 根据构件类别获取构件guid---分页
			* */
void QueryPModelCompByTypePage(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 5)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[3]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[4]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();
	opts->modelID = args[0]->NumberValue();
	opts->compTypeId = args[1]->NumberValue();
	opts->pagenumber = Local<Number>::Cast(args[2])->NumberValue();
	opts->pagecount = Local<Number>::Cast(args[3])->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[4])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, compbytypepage_async_thread_work, compbytypepage_async_thread_callback);
}

/**
 * * 根据属性guid更新一条属性
 * 执行
* **/
void updateprop_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		opts->ok = modelDB->updatePModelProperty(opts->modelID, opts->guid.c_str(), opts->propKey.c_str(), opts->propVal.c_str());
	}
}
/**
* 根据属性guid更新一条属性
* 回调
* */
void updateprop_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[1];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 1, argv);
	}

	delete opts;
}
/**
	* 根据属性guid更新一条属性
	* */
void UpdatePModelProperty(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 5)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	if (!args[4]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg4 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->guid = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->propKey = utf82gbk(LocalObject2char(args[2]->ToString()));
	opts->propVal = utf82gbk(LocalObject2char(args[3]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[4])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, updateprop_async_thread_work, updateprop_async_thread_callback);
}

/**
 * 添加一条构件属性
 * 执行
* **/
void insertprop_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		opts->ok = modelDB->insertPModelProperty(opts->modelID, opts->guid.c_str(), opts->setid.c_str(), opts->propKey.c_str(), opts->propVal.c_str());
	}
}
/**
* 添加一条构件属性
* 回调
* */
void insertprop_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[1];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 1, argv);
	}

	delete opts;
}
/**
 * 添加构件属性
*/
void InsertPModelProperty(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 6)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	if (!args[4]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg4 wrong argument type")));
		return;
	}
	if (!args[5]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg5 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->guid = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->setid = utf82gbk(LocalObject2char(args[2]->ToString()));
	opts->propKey = utf82gbk(LocalObject2char(args[3]->ToString()));
	opts->propVal = utf82gbk(LocalObject2char(args[4]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[5])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, insertprop_async_thread_work, insertprop_async_thread_callback);
}

/**
 * 删除一条构件属性
 * 执行
* **/
void deleteprop_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		opts->ok = modelDB->deletePModelProperty(opts->modelID, opts->guid.c_str(), opts->setid.c_str(), opts->propKey.c_str());
	}
}
/**
* 删除一条构件属性
* 回调
* */
void deleteprop_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[1];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 1, argv);
	}

	delete opts;
}

/**
 * 删除构件属性
*/
void DeletePModelProperty(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 4)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	if (!args[4]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg4 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->guid = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->setid = utf82gbk(LocalObject2char(args[2]->ToString()));
	opts->propKey = utf82gbk(LocalObject2char(args[3]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[4])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, deleteprop_async_thread_work, deleteprop_async_thread_callback);
}

/**
 * 根据Tag查询构件属性
 * 执行
* **/
void tag_compattr_async_thread_work(uv_work_t *args)
{
	ComponentOptions *opts = (ComponentOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompAttr attr;
		bool bQueryCompAttr = modelDB->queryPModelCompAttrByTag(opts->modelID, opts->tag.c_str(), attr);
		opts->ok = bQueryCompAttr;
		if (bQueryCompAttr)
		{
			opts->attr = attr;
		}
	}
}
/**
 * 根据Tag查询构件属性
 * 回调
* */
void tag_compattr_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	ComponentOptions *opts = (ComponentOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? CompAttr2Object(isolate, &(opts->attr)) : v8::Object::New(isolate);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}

/**
 * 通过Tag属性查询构件属性
*/
void QueryPModelCompAttrByTag(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->tag = utf82gbk(LocalObject2char(args[1]->ToString()));
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, tag_compattr_async_thread_work, tag_compattr_async_thread_callback);
}

/**
 * 查询楼层信息
 * 执行
* **/
void query_floors_async_thread_work(uv_work_t *args)
{
	FloorsOptions *opts = (FloorsOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		Floors floors;
		bool bQueryFloors = modelDB->queryPModelFloors(opts->modelID, floors);
		opts->ok = bQueryFloors;
		if (bQueryFloors)
		{
			opts->floors = floors;
		}
	}
}
/**
 * 查询楼层
 * 回调
* */
void query_floors_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	FloorsOptions *opts = (FloorsOptions *)handle->data;
	Local<Value> argv[2];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? Floors2Array(isolate, &(opts->floors)) : v8::Array::New(isolate);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 2, argv);
	}

	delete opts;
}

/**
 * 查询楼层信息
*/
void QueryPModelFloors(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 2)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	// 解析参数
	ComponentOptions *opts = new ComponentOptions();

	opts->modelID = args[0]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[1])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, query_floors_async_thread_work, query_floors_async_thread_callback);
}

/**
 * 分页查询属性
 * 执行
* **/
void floor_comp_async_thread_work(uv_work_t *args)
{
	FloorsOptions *opts = (FloorsOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		CompInfoPage page;
		opts->ok = modelDB->queryPModelCompByFloor_Page(opts->modelID, opts->floorID, opts->pagecount, page);
		if (opts->pagenumber == 0)
		{
			opts->compInfo = page.result;
			opts->totalnumber = page.getTotalNum();
			return;
		}
		//支持直接跳转到某页，没有则返回false
		//默认是pageNo=0， 代表一直往下翻，非0代表直接跳到pageNo页，非法页返回false
		bool bQueryPModelInfo = page.nextPage(opts->pagenumber);
		opts->ok = bQueryPModelInfo;
		if (bQueryPModelInfo)
		{
			opts->compInfo = page.result;
			opts->totalnumber = page.getTotalNum();
		}
	}
}
/**
 * 分页查询属性
 * 回调
* */
void floor_comp_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	FloorsOptions *opts = (FloorsOptions *)handle->data;
	Local<Value> argv[3];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = opts->ok ? Number::New(isolate, opts->totalnumber) : Number::New(isolate, 0);
	argv[2] = opts->ok ? CompInfoVec2Array(isolate, &(opts->compInfo)) : v8::Array::New(isolate, 0);

	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 3, argv);
	}

	delete opts;
}

/**
 * 根据楼层查询构件
*/
void QueryPModelCompByFloorPage(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 5)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	if (!args[4]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg4 wrong argument type")));
		return;
	}
	// 解析参数
	FloorsOptions *opts = new FloorsOptions();
	opts->modelID = args[0]->NumberValue();
	opts->floorID = args[1]->NumberValue();
	opts->pagenumber = args[2]->NumberValue();
	opts->pagecount = args[3]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[4])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, floor_comp_async_thread_work, floor_comp_async_thread_callback);
}

/**
	* 添加某人对PModel的访问权限
	* 执行
	* **/
void auth_add_async_thread_work(uv_work_t *args)
{
	AuthOptions *opts = (AuthOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		opts->accessed = modelDB->addPModelPermission(opts->author.c_str(), opts->modelID);
		opts->ok = true;
	}
}
/*
			* 添加某人对PModel的访问权限
			*/
void AddPModelPermission(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	AuthOptions *opts = new AuthOptions();

	opts->author = utf82gbk(LocalObject2char(args[0]->ToString()));
	;
	opts->modelID = args[1]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, auth_add_async_thread_work, auth_async_thread_callback);
}

/**
			* 去掉某人对PModel的访问权限
			* 执行
			* **/
void auth_remove_async_thread_work(uv_work_t *args)
{
	AuthOptions *opts = (AuthOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		modelDB->removePModelPermission(opts->author.c_str(), opts->modelID);
		opts->ok = true;
	}
}
/**
 * 去掉某人对PModel的访问权限
* **/
void RemovePModelPermission(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsString())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	AuthOptions *opts = new AuthOptions();

	opts->author = utf82gbk(LocalObject2char(args[0]->ToString()));
	opts->modelID = args[1]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, auth_remove_async_thread_work, auth_async_thread_callback);
}

/**
		* 插入时间任务
		* 执行
		* **/
void inserttask_async_thread_work(uv_work_t *args)
{
	AsyncTaskOptions *opts = (AsyncTaskOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		modelDB->insertPModelTask(opts->modelID, opts->opts->GetTask());
		opts->ok = true;
	}
}
/**
		* 插入时间任务
		* 回调
		* */
void task_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	AsyncTaskOptions *opts = (AsyncTaskOptions *)handle->data;
	Local<Value> argv[1];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 1, argv);
	}
	delete opts;
}
/**
	 * 插入时间任务
	*/
void InsertPModelTask(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsObject())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	// 解析参数
	TaskOptions *taskOpts = ObjectWrap::Unwrap<TaskOptions>(args[1]->ToObject());

	AsyncTaskOptions *opts = new AsyncTaskOptions();
	opts->modelID = args[0]->NumberValue();
	opts->opts = taskOpts;
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, inserttask_async_thread_work, task_async_thread_callback);
}

/**
		* 插入时间任务
		* 执行
		* **/
void remove_task_async_thread_work(uv_work_t *args)
{
	AsyncTaskOptions *opts = (AsyncTaskOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		modelDB->removePModelTask(opts->modelID, opts->taskID);
		opts->ok = true;
	}
}

void RemovePModelTask(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 3)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}

	AsyncTaskOptions *opts = new AsyncTaskOptions();
	opts->modelID = args[0]->NumberValue();
	opts->taskID = args[1]->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[2])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, remove_task_async_thread_work, task_async_thread_callback);
}

/**
		* 分页查询模型任务
		* 执行
		* **/
void task_page_async_thread_work(uv_work_t *args)
{
	AsyncTaskOptions *opts = (AsyncTaskOptions *)args->data;
	if (pSource != NULL)
	{
		ModelDB *modelDB = pSource->getModelDB();
		TaskPage page;
		bool bQueryAllTask = modelDB->queryPModelTask_Page(opts->modelID, opts->pagecount, page);
		opts->ok = bQueryAllTask;
		if (opts->pagenumber == 0)
		{
			opts->tasks = page.result;
			opts->totalnumber = page.getTotalNum();
			return;
		}
		//支持直接跳转到某页，没有则返回false
		//默认是pageNo=0， 代表一直往下翻，非0代表直接跳到pageNo页，非法页返回false
		bool bQueryPModelInfo = page.nextPage(opts->pagenumber);
		opts->ok = bQueryPModelInfo;
		if (bQueryPModelInfo)
		{
			opts->tasks = page.result;
			opts->totalnumber = page.getTotalNum();
		}
	}
}
/**
		* 分页查询模型任务
		* 回调
		* */
void task_page_async_thread_callback(uv_work_t *handle, int status)
{
	Isolate *isolate = Isolate::GetCurrent();
	HandleScope scope(isolate);
	AsyncTaskOptions *opts = (AsyncTaskOptions *)handle->data;
	Local<Value> argv[3];
	argv[0] = Null(isolate);
	if (!opts->ok)
	{
		argv[0] = v8::Boolean::New(isolate, true);
	}
	//argv[0] = opts->ok ? Null(isolate) : Boolean::New(isolate, true);
	argv[1] = Number::New(isolate, opts->totalnumber);
	argv[2] = opts->ok ? TaskVec2Array(isolate, &(opts->tasks)) : v8::Array::New(isolate, 0);
	// 执行回调函数
	Local<Function> cb = Local<Function>::New(isolate, opts->finish);
	if (cb->IsFunction())
	{
		cb->Call(isolate->GetCurrentContext()->Global(), 3, argv);
	}

	delete opts;
}
/*
		* 分页查询模型任务
		*/
void QueryPModelTaskPage(const FunctionCallbackInfo<Value> &args)
{
	Isolate *isolate = args.GetIsolate();
	// 验证参数的有效性
	if (args.Length() < 4)
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "wrong number of arguments")));
		return;
	}
	if (!args[0]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg0 wrong argument type")));
		return;
	}
	if (!args[1]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg1 wrong argument type")));
		return;
	}
	if (!args[2]->IsNumber())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg2 wrong argument type")));
		return;
	}
	if (!args[3]->IsFunction())
	{
		isolate->ThrowException(v8::Exception::TypeError(String::NewFromUtf8(isolate, "arg3 wrong argument type")));
		return;
	}
	// 解析参数
	AsyncTaskOptions *opts = new AsyncTaskOptions();
	opts->modelID = args[0]->NumberValue();
	opts->pagenumber = Local<Number>::Cast(args[1])->NumberValue();
	opts->pagecount = Local<Number>::Cast(args[2])->NumberValue();
	opts->finish.Reset(isolate, Local<Function>::New(isolate, Local<Function>::Cast(args[3])));
	opts->work_pool.data = opts;
	uv_queue_work(uv_default_loop(), &opts->work_pool, task_page_async_thread_work, task_page_async_thread_callback);
}
/**
			 * 每个Node模块都需要一个init方法
			* */
void init(v8::Local<Object> exports, v8::Local<Object> module)
{
	NODE_SET_METHOD(exports, "importPModelXmlFile", ImportPModelXmlFile);
	NODE_SET_METHOD(exports, "openDataSource", OpenDataSource);
	NODE_SET_METHOD(exports, "closeDataSource", CloseDataSource);
	NODE_SET_METHOD(exports, "queryPModelInfo", QueryPModelInfo);
	NODE_SET_METHOD(exports, "queryPModelInfoPage", QueryPModelInfoPage);
	NODE_SET_METHOD(exports, "existsPModel", ExistsPModel);
	NODE_SET_METHOD(exports, "hasPModelPermission", HasPModelPermission);
	NODE_SET_METHOD(exports, "queryPModelRootTree", QueryPModelRootTree);
	NODE_SET_METHOD(exports, "queryPModelChildTree", QueryPModelChildTree);
	NODE_SET_METHOD(exports, "queryPModelChildTreePage", QueryPModelChildTreePage);
	// NODE_SET_METHOD(exports, "queryPModelParentTreeByGuid", queryPModelParentTreeByGuid);
	NODE_SET_METHOD(exports, "queryPModelTreeByGuid", QueryPModelTreeByGuid);
	NODE_SET_METHOD(exports, "queryPModelCompAttr", QueryPModelCompAttr);
	NODE_SET_METHOD(exports, "queryPModelCompByProperty", QueryPModelCompByProperty);
	NODE_SET_METHOD(exports, "queryPModelCompByPropertyPage", QueryPModelCompByPropertyPage);
	NODE_SET_METHOD(exports, "queryPModelCompType", QueryPModelCompType);
	NODE_SET_METHOD(exports, "queryPModelCompByType", QueryPModelCompByType);
	NODE_SET_METHOD(exports, "queryPModelCompByTypePage", QueryPModelCompByTypePage);
	NODE_SET_METHOD(exports, "updatePModelProperty", UpdatePModelProperty);
	NODE_SET_METHOD(exports, "insertPModelProperty", InsertPModelProperty);
	NODE_SET_METHOD(exports, "deletePModelProperty", DeletePModelProperty);
	NODE_SET_METHOD(exports, "queryPModelCompAttrByTag", QueryPModelCompAttrByTag);
	NODE_SET_METHOD(exports, "queryPModelFloors", QueryPModelFloors);
	NODE_SET_METHOD(exports, "queryPModelCompByFloorPage", QueryPModelCompByFloorPage);

	NODE_SET_METHOD(exports, "addPModelPermission", AddPModelPermission);
	NODE_SET_METHOD(exports, "removePModelPermission", RemovePModelPermission);

	NODE_SET_METHOD(exports, "insertPModelTask", InsertPModelTask);
	NODE_SET_METHOD(exports, "removePModelTask", RemovePModelTask);
	NODE_SET_METHOD(exports, "queryPModelTaskPage", QueryPModelTaskPage);

	ConnectionOptions::Init(exports);
	TaskOptions::Init(exports);
}
NODE_MODULE(freedatabase, init)

} // namespace freedatabase
